/*******************************************************************************
 * Copyright 2013 Mindaugas Idzelis
 * 
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 * 
 *   http://www.apache.org/licenses/LICENSE-2.0
 * 
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 ******************************************************************************/
package incontrol.plugin;

import static com.google.common.base.Throwables.propagate;
import static com.google.common.util.concurrent.Uninterruptibles.getUninterruptibly;
import incontrol.bf3.state.PlayerList;
import incontrol.bf3.state.PlayerState;
import incontrol.bf3.state.RoundState;
import incontrol.bf3.state.ServerState;
import incontrol.core.Config;
import incontrol.core.protocol.IPluginRequest;
import incontrol.core.protocol.IResponse;
import incontrol.core.protocol.requests.GetRegisteredPlugins;
import incontrol.core.protocol.requests.RetrieveState;
import incontrol.core.protocol.requests.RetrieveState.StateType;
import incontrol.core.protocol.responses.GenericResponse;
import incontrol.plugin.protocol.Channel;
import incontrol.plugin.protocol.EventBus;

import java.util.List;
import java.util.concurrent.ExecutionException;

public class Plugin {

	private EventBus eventBus;

	protected final EventBus getEventBus() {
		return eventBus;
	}

	public final void preInit(Config config, EventBus eventBus) {
		this.eventBus = eventBus;
		init(config);
	}

	public void init(Config config) {

	}

	protected final List<GenericResponse> sendRequest(IPluginRequest request) {
		try {
			int count = (Integer) getUninterruptibly(
					getEventBus().sendServerRequest(
							new GetRegisteredPlugins(request.getClass()
									.getAnnotation(Channel.class).name())))
					.getObject();
			List<GenericResponse> uninterruptibly = getUninterruptibly(getEventBus()
					.sendPluginRequest(request, count));
			return uninterruptibly;
		} catch (ExecutionException e) {
			throw propagate(e);
		}
	}

	protected final void sendResponse(IPluginRequest request, IResponse response) {

		getEventBus().sendServerResponse(request, response);
	}

	protected RoundState getRound() {
		try {
			GenericResponse response = getUninterruptibly(getEventBus()
					.sendServerRequest(new RetrieveState(StateType.ROUND)));
			return (RoundState) response.getObject();
		} catch (ExecutionException e) {
			throw propagate(e);
		}
	}

	protected ServerState getServerState() {
		try {
			GenericResponse response = getUninterruptibly(getEventBus()
					.sendServerRequest(new RetrieveState(StateType.SERVER)));
			return (ServerState) response.getObject();
		} catch (ExecutionException e) {
			throw propagate(e);
		}
	}

	protected PlayerList getPlayerList() {
		try {
			GenericResponse response = getUninterruptibly(getEventBus()
					.sendServerRequest(new RetrieveState(StateType.PLAYERLIST)));
			return (PlayerList) response.getObject();
		} catch (ExecutionException e) {
			throw propagate(e);
		}
	}

	protected PlayerState getPlayerState(String name) {
		try {
			GenericResponse response = getUninterruptibly(getEventBus()
					.sendServerRequest(
							new RetrieveState(StateType.PLAYER, name)));
			return (PlayerState) response.getObject();
		} catch (ExecutionException e) {
			throw propagate(e);
		}
	}
}
